/** * earth-now.co * Author: Simon-Pierre Boucher * Contact: contact@spboucher.ai * File: apps/web/app/metric/[id]/page.tsx * Purpose: Public per-metric page — live counter, real-time model chart and the metric's own methodology */ import type { Metadata } from "next"; import { notFound } from "next/navigation"; import MetricDetail from "@/components/MetricDetail"; import { fetchMetrics, fetchModels } from "@/lib/api"; export const dynamic = "force-dynamic"; interface Params { params: { id: string }; } export async function generateMetadata({ params }: Params): Promise { try { const metrics = await fetchMetrics(); const metric = metrics.find((m) => m.id === params.id); if (metric === undefined) return { title: "earth-now.co" }; return { title: `${metric.name.fr} — earth-now.co`, description: `${metric.name.fr} / ${metric.name.en} — compteur live piloté par un modèle statistique documenté (${metric.model}).`, }; } catch { return { title: "earth-now.co" }; } } export default async function MetricPage({ params }: Params) { let metric; let model = null; try { const [metrics, models] = await Promise.all([fetchMetrics(), fetchModels()]); metric = metrics.find((m) => m.id === params.id); model = models.models[params.id] ?? null; } catch { // API down: 404 rather than a broken page (the dashboard has the offline state). notFound(); } if (metric === undefined) notFound(); return ; }